﻿using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.ComponentModel;
using System.Globalization;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Controls.Primitives;
using System.Windows.Data;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;

namespace Gmantis.Controls
{
    [TemplateVisualState(Name = "Open", GroupName = "DropDownOpenStates"), 
    TemplateVisualState(Name = "Normal", GroupName = "CommonStates"), 
    TemplateVisualState(Name = "Focused", GroupName = "FocusStates"), 
    TemplateVisualState(Name = "Unfocused", GroupName = "FocusStates"), 
    TemplateVisualState(Name = "Valid", GroupName = "ValidationStatesStates"), 
    TemplateVisualState(Name = "InvalidUnfocused", GroupName = "ValidationStatesStates"), 
    TemplateVisualState(Name = "InvalidFocused", GroupName = "ValidationStatesStates"), 
    StyleTypedProperty(Property = "ItemContainerStyle", StyleTargetType = typeof(ComboBoxItem)), 
    StyleTypedProperty(Property = "ScrollBarStyle", StyleTargetType = typeof(ScrollBar)), 
    StyleTypedProperty(Property = "ValidationDecoratorStyle", StyleTargetType = typeof(ValidationDecorator)), 
    TemplateVisualState(Name = "Closed", GroupName = "DropDownOpenStates"), 
    TemplateVisualState(Name = "MouseOver", GroupName = "CommonStates"), 
    TemplateVisualState(Name = "Disabled", GroupName = "CommonStates"), 
    TemplatePart(Name = "ComboHeader", Type = typeof(TextEditableContentControl)), 
    TemplatePart(Name = "ScrollViewer", Type = typeof(System.Windows.Controls.ScrollViewer)), 
    TemplatePart(Name = "DropDown", Type = typeof(DropDown)), 
    TemplatePart(Name = "HeaderClickInterceptor", Type = typeof(FrameworkElement))]
    public class ComboBox : System.Windows.Controls.ItemsControl
    {
        // Fields
        private bool _changed;
        private bool _changeItemsInternal;
        private int _desiredIndex;
        private bool _displayDDL;
        public TextEditableContentControl _elementComboHeader;
        internal DropDown _elementDropDown;
        internal FrameworkElement _elementHeaderClickInterceptor;
        internal System.Windows.Controls.ScrollViewer _elementScrollViewer;
        private ComboBoxItem _filterItem;
        private List<object> _filterItems;
        internal bool _isLoaded;
        internal bool _isSettingText;
        private bool _itemClick;
        private ComboBoxItemConverterBridge _myConverterBridge;
        private bool _setting;
        private List<object> _tempItems;
        private bool _throwIsDropDownOpenChanged;
        private bool _throwIsMouseOverChanged;
        private bool _throwSelectedIndexChanged;
        private bool _throwSelectedItemChanged;
        private bool _throwSelectedValueChanged;
        public static readonly DependencyProperty AutoCompleteProperty;
        public static readonly DependencyProperty ButtonBackgroundProperty;
        public static readonly DependencyProperty ButtonForegroundProperty;
        public static readonly DependencyProperty CaretBrushProperty;
        internal const string ComboHeaderElementName = "ComboHeader";
        public static readonly DependencyProperty ConditionProperty;
        public static readonly DependencyProperty CornerRadiusProperty;
        private const string DefaultDataTrmplateDisplayMemberPath = "<DataTemplate xmlns=\"http://schemas.microsoft.com/winfx/2006/xaml/presentation\" xmlns:x=\"http://schemas.microsoft.com/winfx/2006/xaml\"> <ContentPresenter Content=\"{0}\" /> </DataTemplate>";
        
        public static readonly DependencyProperty DisabledCuesVisibilityProperty;
        private static readonly DependencyProperty DisplayMemberPathShadowProperty;
        public static readonly DependencyProperty DropDownDirectionProperty;
        internal const string DropDownElementName = "DropDown";
        public static readonly DependencyProperty DropDownHeightProperty;
        public static readonly DependencyProperty DropDownWidthProperty;
        public static readonly DependencyProperty FocusBrushProperty;
        public static readonly DependencyProperty FocusCuesVisibilityProperty;
        internal static readonly DependencyProperty ForceMouseOverProperty;
        internal const string HeaderClickInterceptorElementName = "HeaderClickInterceptor";
        public static readonly DependencyProperty IsDropDownOpenProperty;
        public static readonly DependencyProperty IsEditableProperty;
        public static readonly DependencyProperty IsFocusedProperty;
        private bool isFound;
        public static readonly DependencyProperty IsMouseOverProperty;
        public static readonly DependencyProperty ItemContainerStyleProperty;
        public static readonly DependencyProperty ItemConverterProperty;
        public static readonly DependencyProperty ItemTemplateSelectorProperty;
        private static readonly DependencyProperty ItemTemplateShadowProperty;
        private int lastDelete;
        public static readonly DependencyProperty MaxDropDownHeightProperty;
        public static readonly DependencyProperty MaxDropDownWidthProperty;
        public static readonly DependencyProperty MouseOverBrushProperty;
        internal const int NOTHING_SELECTED_INDEX = -1;
        public static readonly DependencyProperty PressedBrushProperty;
        public static readonly DependencyProperty ScrollBarStyleProperty;
        internal const string ScrollViewerElementName = "ScrollViewer";
        private static readonly DependencyProperty ScrollViewerViewportHeightShadowProperty;
        public static readonly DependencyProperty SelectedBackgroundProperty;
        public static readonly DependencyProperty SelectedIndexProperty;
        public static readonly DependencyProperty SelectedItemProperty;
        public static readonly DependencyProperty SelectedValuePathProperty;
        public static readonly DependencyProperty SelectedValueProperty;
        public static readonly DependencyProperty SelectionBackgroundProperty;
        public static readonly DependencyProperty SelectionForegroundProperty;
        private ComboBoxItem SwappedOutItem;
        public static readonly DependencyProperty TextAlignmentProperty;
        public static readonly DependencyProperty TextProperty;
        public static readonly DependencyProperty ValidationDecoratorStyleProperty;
        public static readonly DependencyProperty WatermarkProperty;

        // Events
        public event EventHandler EditCompleted;

        public event EventHandler<PropertyChangedEventArgs<bool>> IsDropDownOpenChanged;

        public event EventHandler<PropertyChangedEventArgs<bool>> IsMouseOverChanged;

        public event Func<Key, int, int> KeyDownInPopup;

        public event EventHandler<PropertyChangedEventArgs<int>> SelectedIndexChanged;

        public event EventHandler<PropertyChangedEventArgs<object>> SelectedItemChanged;

        public event EventHandler<PropertyChangedEventArgs<object>> SelectedValueChanged;

        public event EventHandler<PropertyChangedEventArgs<object>> SelectionCommitted;

        public event EventHandler<ValidateInputEventArgs> ValidateInput;

        // Methods
        static ComboBox()
        {
            DisplayMemberPathShadowProperty = DependencyProperty.Register("DisplayMemberPathShadow", typeof(object), typeof(ComboBox), new PropertyMetadata((s, e) => ((ComboBox)s).UpdateHeaderTemplate()));
            ItemTemplateShadowProperty = DependencyProperty.Register("ItemTemplateShadow", typeof(object), typeof(ComboBox), new PropertyMetadata((s, e) => ((ComboBox)s).UpdateHeaderTemplate()));
            ScrollViewerViewportHeightShadowProperty = DependencyProperty.Register("ScrollViewerViewportHeightShadow", typeof(double), typeof(ComboBox), new PropertyMetadata(delegate(DependencyObject s, DependencyPropertyChangedEventArgs e)
            {
                Action a = null;
                ComboBox this_ = (ComboBox)s;
                if (this_._elementScrollViewer.VerticalOffset == ((this_.SelectedIndex - ((double)e.OldValue)) + 1.0))
                {
                    if (a == null)
                    {
                        a = () => this_.ScrollSelectedIntoView();
                    }
                    this_.Dispatcher.BeginInvoke(a);
                }
            }));
            ItemTemplateSelectorProperty = DependencyProperty.Register("ItemTemplateSelector", typeof(DataTemplateSelector), typeof(ComboBox), new PropertyMetadata(null));
            SelectedItemProperty = DependencyProperty.Register("SelectedItem", typeof(object), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnSelectedItemPropertyChanged)));
            SelectedIndexProperty = DependencyProperty.Register("SelectedIndex", typeof(int), typeof(ComboBox), new PropertyMetadata(-1, new PropertyChangedCallback(ComboBox.OnSelectedIndexPropertyChanged)));
            SelectedValuePathProperty = DependencyProperty.Register("SelectedValuePath", typeof(string), typeof(ComboBox), null);
            SelectedValueProperty = DependencyProperty.Register("SelectedValue", typeof(object), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnSelectedValuePropertyChanged)));
            TextProperty = DependencyProperty.Register("Text", typeof(string), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnTextPropertyChanged)));
            ItemConverterProperty = DependencyProperty.Register("ItemConverter", typeof(TypeConverter), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnItemConverterPropertyChanged)));
            AutoCompleteProperty = DependencyProperty.Register("AutoComplete", typeof(bool), typeof(ComboBox), new PropertyMetadata(true, new PropertyChangedCallback(ComboBox.OnAutoCompletePropertyChanged)));
            IsEditableProperty = DependencyProperty.Register("IsEditable", typeof(bool), typeof(ComboBox), new PropertyMetadata(false, new PropertyChangedCallback(ComboBox.OnIsEditablePropertyChanged)));
            WatermarkProperty = DependencyProperty.Register("Watermark", typeof(object), typeof(ComboBox), null);
            ItemContainerStyleProperty = DependencyProperty.Register("ItemContainerStyle", typeof(Style), typeof(ComboBox), null);
            TextAlignmentProperty = DependencyProperty.Register("TextAlignment", typeof(TextAlignment), typeof(ComboBox), null);
            IsDropDownOpenProperty = DependencyProperty.Register("IsDropDownOpen", typeof(bool), typeof(ComboBox), new PropertyMetadata(false, new PropertyChangedCallback(ComboBox.OnIsDropDownOpenPropertyChanged)));
            DropDownHeightProperty = DependencyProperty.Register("DropDownHeight", typeof(double), typeof(ComboBox), new PropertyMetadata(double.NaN));
            DropDownWidthProperty = DependencyProperty.Register("DropDownWidth", typeof(double), typeof(ComboBox), new PropertyMetadata(double.NaN));
            MaxDropDownHeightProperty = DependencyProperty.Register("MaxDropDownHeight", typeof(double), typeof(ComboBox), new PropertyMetadata(226.0));
            MaxDropDownWidthProperty = DependencyProperty.Register("MaxDropDownWidth", typeof(double), typeof(ComboBox), new PropertyMetadata(double.MaxValue));
            DropDownDirectionProperty = DependencyProperty.Register("DropDownDirection", typeof(DropDownDirection), typeof(ComboBox), new PropertyMetadata(DropDownDirection.BelowOrAbove));
            ScrollBarStyleProperty = DependencyProperty.Register("ScrollBarStyle", typeof(Style), typeof(ComboBox), null);
            CornerRadiusProperty = DependencyProperty.Register("CornerRadius", typeof(CornerRadius), typeof(ComboBox), null);
            CaretBrushProperty = DependencyProperty.Register("CaretBrush", typeof(Brush), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnCaretBrushPropertyChanged)));
            ConditionProperty = DependencyProperty.Register("Condition", typeof(Condition), typeof(ComboBox), new PropertyMetadata(Condition.StartWith, new PropertyChangedCallback(ComboBox.OnConditionPropertyChanged)));
            FocusCuesVisibilityProperty = DependencyProperty.Register("FocusCuesVisibility", typeof(Visibility), typeof(ComboBox), new PropertyMetadata(Visibility.Visible));
            DisabledCuesVisibilityProperty = DependencyProperty.Register("DisabledCuesVisibility", typeof(Visibility), typeof(ComboBox), new PropertyMetadata(Visibility.Visible));
            IsMouseOverProperty = DependencyProperty.Register("IsMouseOver", typeof(bool), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnIsMouseOverPropertyChanged)));
            ForceMouseOverProperty = DependencyProperty.Register("ForceMouseOver", typeof(bool), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnForceMouseOverPropertyChanged)));
            IsFocusedProperty = DependencyProperty.Register("IsFocused", typeof(bool), typeof(ComboBox), new PropertyMetadata(new PropertyChangedCallback(ComboBox.OnIsFocusedPropertyChanged)));
            ValidationDecoratorStyleProperty = DependencyProperty.Register("ValidationDecoratorStyle", typeof(Style), typeof(ComboBox), null);
            MouseOverBrushProperty = DependencyProperty.Register("MouseOverBrush", typeof(Brush), typeof(ComboBox), null);
            SelectionBackgroundProperty = DependencyProperty.Register("SelectionBackground", typeof(Brush), typeof(ComboBox), null);
            SelectionForegroundProperty = DependencyProperty.Register("SelectionForeground", typeof(Brush), typeof(ComboBox), null);
            SelectedBackgroundProperty = DependencyProperty.Register("SelectedBackground", typeof(Brush), typeof(ComboBox), null);
            PressedBrushProperty = DependencyProperty.Register("PressedBrush", typeof(Brush), typeof(ComboBox), null);
            FocusBrushProperty = DependencyProperty.Register("FocusBrush", typeof(Brush), typeof(ComboBox), null);
            ButtonBackgroundProperty = DependencyProperty.Register("ButtonBackground", typeof(Brush), typeof(ComboBox), null);
            ButtonForegroundProperty = DependencyProperty.Register("ButtonForeground", typeof(Brush), typeof(ComboBox), null);
        }

        public ComboBox()
        {
            RoutedEventHandler handler = null;
            DependencyPropertyChangedEventHandler handler2 = null;
            this._desiredIndex = -1;
            this._tempItems = new List<object>();
            this._filterItems = new List<object>();
            this.lastDelete = 2;
            this._throwSelectedItemChanged = true;
            this._throwSelectedIndexChanged = true;
            this._throwSelectedValueChanged = true;
            this._throwIsDropDownOpenChanged = true;
            this._throwIsMouseOverChanged = true;
            base.DefaultStyleKey = typeof(ComboBox);
            if (handler == null)
            {
                handler = delegate(object param0, RoutedEventArgs param1)
                {
                    this.ChangeVisualStateDropDownOpen(false);
                    this.ChangeVisualStateCommon(false);
                    this.ChangeVisualStateFocus(false);
                };
            }
            base.Loaded += handler;
            if (handler2 == null)
            {
                handler2 = (s, a) => this.ChangeVisualStateCommon(true);
            }
            base.IsEnabledChanged += handler2;
            base.GotFocus += new RoutedEventHandler(this.Control_GotFocus);
            base.LostFocus += new RoutedEventHandler(this.Control_LostFocus);
            base.MouseEnter += new MouseEventHandler(this.Control_MouseEnter);
            base.MouseLeave += new MouseEventHandler(this.Control_MouseLeave);
            this.SetCustomDefaultValues();

        }

        private void _elementComboHeader_LostFocus(object sender, RoutedEventArgs e)
        {
            Action action = null;
            if (this._isLoaded && !this.IsVisualOrLogicalParentOf(this._elementComboHeader.GetLogicalFocusedElement()))
            {
                if (action == null)
                {
                    action = delegate
                    {
                        this._elementComboHeader.IsTabStop = false;
                        base.IsTabStop = true;
                    };
                }
                this.BeginInvoke(action);
            }
        }

        public void BeginEdit(string text)
        {
            this.SetTextInput(this.Text, text, true);
        }

        private void ComboBox_MouseWheel(object sender, MouseWheelEventArgs e)
        {
            double num = e.Delta * 20.0;
            double offset = this._elementScrollViewer.VerticalOffset - num;
            if (offset > this._elementScrollViewer.ScrollableHeight)
            {
                offset = this._elementScrollViewer.ScrollableHeight;
            }
            else if (offset < 0.0)
            {
                offset = 0.0;
            }
            this._elementScrollViewer.ScrollToVerticalOffset(offset);
            e.Handled = true;
        }

        private void Control_GotFocus(object sender, RoutedEventArgs e)
        {
            this.IsFocused = true;
        }

        private void Control_LostFocus(object sender, RoutedEventArgs e)
        {
            this.IsFocused = false;
        }

        private void Control_MouseEnter(object sender, MouseEventArgs e)
        {
            if (InputEventArgs.GetPointerType(e) == PointerDeviceType.Mouse)
            {
                this.IsMouseOver = true;
            }
        }

        private void Control_MouseLeave(object sender, MouseEventArgs e)
        {
            if (InputEventArgs.GetPointerType(e) == PointerDeviceType.Mouse)
            {
                this.IsMouseOver = false;
            }
        }

        protected void ChangeVisualStateCommon(bool useTransitions)
        {
            if (!base.IsEnabled)
            {
                VisualStateHelper.GoToState(this, "Disabled", useTransitions);
            }
            if (base.IsEnabled)
            {
                VisualStateHelper.GoToState(this, "MouseOver", useTransitions);
            }
            if ((base.IsEnabled && !this.IsMouseOver) && !this.ForceMouseOver)
            {
                VisualStateHelper.GoToState(this, "Normal", useTransitions);
            }
        }

        protected void ChangeVisualStateDropDownOpen(bool useTransitions)
        {
            if (!this.IsDropDownOpen)
            {
                VisualStateHelper.GoToState(this, "Closed", useTransitions);
            }
            if (this.IsDropDownOpen)
            {
                VisualStateHelper.GoToState(this, "Open", useTransitions);
            }
        }

        protected void ChangeVisualStateFocus(bool useTransitions)
        {
            if (!this.IsFocused)
            {
                VisualStateHelper.GoToState(this, "Unfocused", useTransitions);
            }
            if (this.IsFocused)
            {
                VisualStateHelper.GoToState(this, "Focused", useTransitions);
            }
        }

        private void ClearFilterItemVisualState()
        {
            if (this._filterItem != null)
            {
                this._filterItem.ChangeVisualStateCondition(false, true);
                this._filterItem = null;
            }
        }

        private static Brush CloneBrush(Brush source)
        {
            Brush brush = null;
            if (source != null)
            {
                if (source is SolidColorBrush)
                {
                    SolidColorBrush brush2 = source as SolidColorBrush;
                    return new SolidColorBrush(brush2.Color);
                }
                if (!(source is GradientBrush))
                {
                    return brush;
                }
                GradientBrush brush3 = source as GradientBrush;
                if (source is LinearGradientBrush)
                {
                    LinearGradientBrush brush4 = source as LinearGradientBrush;
                    LinearGradientBrush brush5 = new LinearGradientBrush
                    {
                        StartPoint = brush4.StartPoint,
                        EndPoint = brush4.EndPoint
                    };
                    brush = brush5;
                }
                else
                {
                    RadialGradientBrush brush6 = source as RadialGradientBrush;
                    RadialGradientBrush brush7 = new RadialGradientBrush
                    {
                        Center = brush6.Center,
                        GradientOrigin = brush6.GradientOrigin,
                        RadiusX = brush6.RadiusX,
                        RadiusY = brush6.RadiusY
                    };
                    brush = brush7;
                }
                GradientBrush brush8 = brush as GradientBrush;
                brush8.ColorInterpolationMode = brush3.ColorInterpolationMode;
                brush8.MappingMode = brush3.MappingMode;
                brush8.RelativeTransform = brush3.RelativeTransform;
                brush8.SpreadMethod = brush3.SpreadMethod;
                brush8.Transform = brush3.Transform;
                foreach (GradientStop stop in brush3.GradientStops)
                {
                    GradientStop stop2 = new GradientStop
                    {
                        Offset = stop.Offset,
                        Color = stop.Color
                    };
                    brush8.GradientStops.Add(stop2);
                }
            }
            return brush;
        }

        private ComboBoxItem ComboBoxItemFromItem(object item)
        {
            ComboBoxItem item2 = item as ComboBoxItem;
            if (item2 != null)
            {
                return item2;
            }
            return (ComboBoxItem)base.ItemContainerGenerator.ContainerFromItem(item);
        }

        internal int DoCircularSearch(Func<string, bool> doComparission)
        {
            int num = (this.SelectedIndex == -1) ? 0 : this.SelectedIndex;
            for (int i = 0; i < base.Items.Count; i++)
            {
                int num3 = Math.Max(0, num + i) % base.Items.Count;
                object obj2 = base.Items[num3];
                if (this.ItemConverter != null)
                {
                    string arg = this._myConverterBridge.ConvertToString(obj2);
                    if (doComparission(arg))
                    {
                        return num3;
                    }
                }
            }
            return -1;
        }

        private void dropdown_IsDropDownOpenChanged(object sender, PropertyChangedEventArgs<bool> e)
        {
            this.IsDropDownOpen = this._elementDropDown.IsDropDownOpen;
        }

        private int FindString(string inputText, bool executeExactMatching, bool executeStartsWith)
        {
            Func<string, bool> doComparission = null;
            Func<string, bool> func2 = null;
            if (string.IsNullOrEmpty(inputText))
            {
                return -1;
            }
            if (executeExactMatching)
            {
                int num = -1;
                if (doComparission == null)
                {
                    doComparission = item => string.Compare(item, inputText, StringComparison.OrdinalIgnoreCase) == 0;
                }
                num = this.DoCircularSearch(doComparission);
                if (num != -1)
                {
                    return num;
                }
            }
            if (!executeStartsWith)
            {
                return -1;
            }
            if (func2 == null)
            {
                func2 = item => item.StartsWith(inputText, StringComparison.OrdinalIgnoreCase);
            }
            return this.DoCircularSearch(func2);
        }

        private bool FindString(string inputText, bool executeExactMatching, bool executeStartsWith, out string outputText)
        {
            outputText = string.Empty;
            int num = this.FindString(inputText, executeExactMatching, executeStartsWith);
            if (num == -1)
            {
                return false;
            }
            outputText = this._myConverterBridge.ConvertToString(base.Items[num]);
            if (this.IsDropDownOpen && (this.SelectedIndex != num))
            {
                this.SelectedIndex = num;
            }
            return true;
        }

        protected override DependencyObject GetContainerForItemOverride()
        {
            return new ComboBoxItem();
        }

        private DataTemplate GetDefaultDataTemplate()
        {
            if (base.DisplayMemberPath == null)
            {
                return null;
            }
            if (base.DisplayMemberPath == ".")
            {
                return null;
            }
            if (base.DisplayMemberPath == "")
            {
                return null;
            }
            return PlatformIndependent.LoadXaml<DataTemplate>(string.Format("<DataTemplate xmlns=\"http://schemas.microsoft.com/winfx/2006/xaml/presentation\" xmlns:x=\"http://schemas.microsoft.com/winfx/2006/xaml\"> <ContentPresenter Content=\"{0}\" /> </DataTemplate>", "{Binding " + base.DisplayMemberPath + "}"));
        }

        private T GetTemplateChild<T>(string childName, bool required, ref string errors) where T : class
        {
            DependencyObject templateChild = base.GetTemplateChild(childName);
            ApplyTemplateHelper.VerifyTemplateChild(typeof(T), "template part", childName, templateChild, required, ref errors);
            return (templateChild as T);
        }

        private static Storyboard GetTemplateChildResource(FrameworkElement root, string resourceName, bool required, ref string errors)
        {
            return GetTemplateChildResource<Storyboard>(root, resourceName, required, ref errors);
        }

        private static T GetTemplateChildResource<T>(FrameworkElement root, string resourceName, bool required, ref string errors) where T : class
        {
            object child = root.Resources[resourceName];
            ApplyTemplateHelper.VerifyTemplateChild(typeof(T), "resource", resourceName, child, required, ref errors);
            return (child as T);
        }

        private void handle_ItemClick(object sender, MouseButtonEventArgs e)
        {
            this.ClearFilterItemVisualState();
            ComboBoxItem item = (ComboBoxItem)sender;
            object obj2 = item.Item ?? item;
            this._itemClick = true;
            this.SelectedItem = obj2;
            this._itemClick = false;
            item.IsMouseOver = false;
            this.IsDropDownOpen = false;
            this.OnEditCompleted();
        }

        private void header_AutoComplete(object sender, TextEditedEventArgs e)
        {
            if (base.IsEnabled)
            {
                if (this.AutoComplete && (this.Condition == Condition.StartWith))
                {
                    string str;
                    this.lastDelete = ((e.LastKey == Key.Delete) || (e.LastKey == Key.Back)) ? 0 : (this.lastDelete + 1);
                    if (this.lastDelete < 1)
                    {
                        return;
                    }
                    if (this.FindString(e.CurrentText, true, true, out str))
                    {
                        this.isFound = true;
                        e.NewText = str;
                        e.NewSelectionStart = e.CurrentText.Length;
                        return;
                    }
                    this.isFound = false;
                }
                if (this.IsEditable)
                {
                    e.NewText = e.CurrentText;
                    e.NewSelectionStart = e.CurrentSelectionStart;
                }
                else if (this.Condition != Condition.Contains)
                {
                    e.Cancel = true;
                }
            }
        }

        private void header_EditCanceled(object sender, EventArgs e)
        {
            this._setting = true;
            this.Text = this._elementComboHeader.EditTextBox.Text;
            this._setting = false;
        }

        private void header_EditCompleted(object sender, EventArgs e)
        {
            this.SetTextInput(this.Text, this._elementComboHeader.EditTextBox.Text, false);
            this.OnEditCompleted();
        }

        private void header_Filter(object sender, TextEditedEventArgs e)
        {
            Func<string, bool> doComparission = null;
            Action a = null;
            if ((this.Condition == Condition.Contains) && !this._itemClick)
            {
                if (((e.LastKey == Key.Delete) || (e.LastKey == Key.Back)) && string.IsNullOrEmpty(e.CurrentText))
                {
                    this.ReloadItems();
                    this.SelectedIndex = -1;
                    this.ClearFilterItemVisualState();
                }
                else
                {
                    if (doComparission == null)
                    {
                        doComparission = item => item.IndexOf(e.CurrentText, StringComparison.OrdinalIgnoreCase) >= 0;
                    }
                    if ((this.DoCircularSearch(doComparission) < 0) && !this.IsEditable)
                    {
                        e.Cancel = true;
                        return;
                    }
                    this.ReloadItems();
                    this.SelectedItem = null;
                    if (base.ItemsSource != null)
                    {
                        this._filterItems.Clear();
                        foreach (object obj2 in base.ItemsSource)
                        {
                            if ((this.ItemConverter != null) && (this._myConverterBridge.ConvertToString(obj2).IndexOf(e.CurrentText, StringComparison.OrdinalIgnoreCase) >= 0))
                            {
                                this._filterItems.Add(obj2);
                            }
                        }
                        this._changeItemsInternal = true;
                        base.ItemsSource = this._filterItems;
                        this._changeItemsInternal = false;
                    }
                    else
                    {
                        for (int j = 0; j < base.Items.Count; j++)
                        {
                            object obj3 = base.Items[j];
                            if ((this.ItemConverter != null) && (this._myConverterBridge.ConvertToString(obj3).IndexOf(e.CurrentText, StringComparison.OrdinalIgnoreCase) < 0))
                            {
                                this._changeItemsInternal = true;
                                base.Items.Remove(obj3);
                                this._changeItemsInternal = false;
                                j--;
                            }
                        }
                    }
                    if (base.Items.Count > 0)
                    {
                        base.UpdateLayout();
                        this._displayDDL = true;
                        this.IsDropDownOpen = true;
                        this._displayDDL = false;
                        if (a == null)
                        {
                            a = delegate
                            {
                                this.ClearFilterItemVisualState();
                                this._filterItem = this.ComboBoxItemFromItem(base.Items[0]);
                                if (this._filterItem != null)
                                {
                                    bool flag = false;
                                    for (int k = 0; k < base.Items.Count; k++)
                                    {
                                        if (base.Items[k] == this.SelectedItem)
                                        {
                                            flag = true;
                                            break;
                                        }
                                    }
                                    if (!flag)
                                    {
                                        this._filterItem.ChangeVisualStateCondition(true, true);
                                    }
                                }
                            };
                        }
                        base.Dispatcher.BeginInvoke(a);
                    }
                    else
                    {
                        this._displayDDL = true;
                        this.IsDropDownOpen = false;
                        this._displayDDL = false;
                    }
                }
                if (string.IsNullOrEmpty(e.CurrentText))
                {
                    this.SelectedItem = null;
                    this.IsDropDownOpen = false;
                }
            }
        }

        private void header_IsValidInput(object sender, ValidateInputEventArgs e)
        {
            if (string.IsNullOrEmpty(e.Input) && this._setting)
            {
                e.IsValidInput = true;
            }
            else if (!this.IsEditable || (this.Condition == Condition.Contains))
            {
                string str;
                bool flag = this.FindString(e.Input, true, false, out str);
                e.IsValidInput = (e.Input == str) && flag;
            }
            else if (this.ValidateInput != null)
            {
                this.ValidateInput(this, e);
            }
        }

        private void header_TextBoxKeyDown(object sender, System.Windows.Input.KeyEventArgs e)
        {
            if (!this.IsDropDownOpen && this.IsOpenKey(e.Key))
            {
                this.IsDropDownOpen = true;
                this._elementComboHeader.IsInEditMode = true;
                e.Handled = true;
            }
            else
            {
                int num;
                if (this.MoveListBox(e.Key, out num))
                {
                    if (num != this.SelectedIndex)
                    {
                        this.SelectedIndex = num;
                    }
                    this._elementComboHeader.IsInEditMode = true;
                    e.Handled = true;
                }
                if ((e.Key == Key.Enter) && this.IsDropDownOpen)
                {
                    e.Handled = true;
                }
            }
        }

        private void header_TextBoxKeyUp(object sender, System.Windows.Input.KeyEventArgs e)
        {
            Key key = e.Key;
            if (key != Key.Enter)
            {
                if (key != Key.Escape)
                {
                    if ((key == Key.F4) && !KeyboardUtil.Alt)
                    {
                        this.IsDropDownOpen = !this.IsDropDownOpen;
                        e.Handled = true;
                    }
                    return;
                }
            }
            else
            {
                if (((this._filterItem != null) && (this.SelectedItem == null)) && ((this.Condition == Condition.Contains) && (base.Items.Count > 0)))
                {
                    this.SelectedItem = base.Items[0];
                    this._filterItem.ChangeVisualStateCondition(false, true);
                    this._filterItem = null;
                }
                if (this.IsDropDownOpen)
                {
                    this.IsDropDownOpen = false;
                }
                this._elementComboHeader.IsInEditMode = false;
                this._elementComboHeader.IsInEditMode = true;
                if (!this.isFound)
                {
                    this._elementComboHeader._elementEditControl.Select(this._elementComboHeader._elementEditControl.Text.Length, 0);
                }
                e.Handled = true;
                return;
            }
            if (this.IsDropDownOpen)
            {
                this.IsDropDownOpen = false;
                this._elementComboHeader.IsInEditMode = true;
                e.Handled = true;
            }
        }

        private void InitializeComboHeaderPart()
        {
            this._elementComboHeader.IsTabStop = false;
            this._elementComboHeader.SeparateActualContent = true;
            this._elementComboHeader.TextBoxKeyDown += new EventHandler<System.Windows.Input.KeyEventArgs>(this.header_TextBoxKeyDown);
            this._elementComboHeader.TextBoxKeyUp += new EventHandler<System.Windows.Input.KeyEventArgs>(this.header_TextBoxKeyUp);
            this._elementComboHeader.BindInputMethodProperties(this);
            this._elementComboHeader.TextEdited += new EventHandler<TextEditedEventArgs>(this.header_AutoComplete);
            this._elementComboHeader.TextEdited += new EventHandler<TextEditedEventArgs>(this.header_Filter);
            this._elementComboHeader.EditCompleted += new EventHandler(this.header_EditCompleted);
            this._elementComboHeader.EditCanceled += new EventHandler(this.header_EditCanceled);
            this._elementComboHeader.ValidateInput += new EventHandler<ValidateInputEventArgs>(this.header_IsValidInput);
            this._elementComboHeader.SetBinding(TextEditableContentControl.WatermarkProperty, new Binding().From<ComboBox>(this, x => x.Watermark));
            this.UpdateIsReadOnly();
        }

        private void InitializeDropDownPart()
        {
            this._elementDropDown.AutoClose = true;
            this._elementDropDown.IsDropDownOpen = this.IsDropDownOpen;
            //if (this.DropDownHeight == 0.0)
            //    this.DropDownHeight = this._elementDropDown.DropDownHeight;
            //if (this.DropDownWidth == 0.0)
            //    this.DropDownWidth = this._elementDropDown.DropDownWidth;
            this._elementDropDown.IsDropDownOpenChanged += new EventHandler<PropertyChangedEventArgs<bool>>(this.dropdown_IsDropDownOpenChanged);
            this.UpdateMinDropDownWidth();
        }

        private void InitializeHeaderClickInterceptorPart()
        {
            this.UpdateHeaderClickInterceptor();
            this._elementHeaderClickInterceptor.MouseLeftButtonDown += (param0, param1) => this.IsDropDownOpen = !this.IsDropDownOpen;
        }

        private void InitializeScrollViewerPart()
        {
            this._elementScrollViewer.IsTabStop = false;
            new MouseHelper(this._elementScrollViewer).MouseWheel += new EventHandler<MouseWheelEventArgs>(this.ComboBox_MouseWheel);
            base.SetBinding(ScrollViewerViewportHeightShadowProperty, new Binding().From<System.Windows.Controls.ScrollViewer>(this._elementScrollViewer, x => x.ViewportHeight));
        }

        protected override bool IsItemItsOwnContainerOverride(object item)
        {
            return (item is ComboBoxItem);
        }

        internal bool IsOnCurrentPage(int index)
        {
            GeneralTransform transform;
            ComboBoxItem reference = base.ItemContainerGenerator.ContainerFromIndex(index) as ComboBoxItem;
            if (reference == null)
            {
                return false;
            }
            Panel parent = VisualTreeHelper.GetParent(reference) as Panel;
            if (parent == null)
            {
                return false;
            }
            Rect rect = new Rect(0.0, 0.0, parent.ActualWidth, parent.ActualHeight);
            try
            {
                transform = reference.TransformToVisual(parent);
            }
            catch
            {
                return false;
            }
            Rect rect2 = new Rect(transform.Transform(new Point()), transform.Transform(new Point(reference.ActualWidth, reference.ActualHeight)));
            return ((rect.Top <= rect2.Top) && (rect2.Bottom <= rect.Bottom));
        }

        protected virtual bool IsOpenKey(Key key)
        {
            return ((key == Key.Down) && KeyboardUtil.Ctrl);
        }

        private bool IsSelectable(int index)
        {
            ComboBoxItem item = base.Items[index] as ComboBoxItem;
            return ((item == null) || (item.IsEnabled && (item.Visibility == Visibility.Visible)));
        }

        protected virtual bool MoveListBox(Key key, out int newIndex)
        {
            int selectedIndex = this.SelectedIndex;
            newIndex = this.SelectedIndex;
            if (this.KeyDownInPopup != null)
            {
                int num2 = this.KeyDownInPopup(key, selectedIndex);
                if ((num2 < base.Items.Count) && (num2 >= 0))
                {
                    newIndex = num2;
                    return true;
                }
            }
            else
            {
                int viewportHeight = (int)this._elementScrollViewer.ViewportHeight;
                switch (key)
                {
                    case Key.PageUp:
                        if (!this.IsDropDownOpen)
                        {
                            break;
                        }
                        if ((selectedIndex - viewportHeight) >= 0)
                        {
                            newIndex = selectedIndex - viewportHeight;
                        }
                        else
                        {
                            newIndex = 0;
                        }
                        return true;

                    case Key.PageDown:
                        if (!this.IsDropDownOpen)
                        {
                            break;
                        }
                        if ((selectedIndex + viewportHeight) < base.Items.Count)
                        {
                            newIndex = selectedIndex + viewportHeight;
                        }
                        else
                        {
                            newIndex = base.Items.Count - 1;
                        }
                        return true;

                    case Key.End:
                        if (!this.IsDropDownOpen || this.IsEditable)
                        {
                            break;
                        }
                        newIndex = base.Items.Count - 1;
                        return true;

                    case Key.Home:
                        if (!this.IsDropDownOpen || this.IsEditable)
                        {
                            break;
                        }
                        newIndex = 0;
                        return true;

                    case Key.Up:
                    Label_009F:
                        if (selectedIndex > 0)
                        {
                            selectedIndex--;
                            if (!this.IsSelectable(selectedIndex))
                            {
                                goto Label_009F;
                            }
                            newIndex = selectedIndex;
                        }
                        return true;

                    case Key.Down:
                    Label_007F:
                        selectedIndex++;
                        if (selectedIndex < base.Items.Count)
                        {
                            if (!this.IsSelectable(selectedIndex))
                            {
                                goto Label_007F;
                            }
                            newIndex = selectedIndex;
                        }
                        return true;
                }
            }
            return false;
        }

        private int MyIndexOf(object value)
        {
            if (value != null)
            {
                if (value.GetType() == typeof(string))
                {
                    return this.FindString((string)value, true, false);
                }
                for (int i = 0; i < base.Items.Count; i++)
                {
                    object obj2 = base.Items[i];
                    if (obj2.Equals(value))
                    {
                        return i;
                    }
                }
            }
            return -1;
        }

        private void OnAfterApplyTemplate()
        {
            this._elementComboHeader.ContentConverter = this._myConverterBridge;
            this.UpdateSwappedOut();
            this.UpdateHeaderTemplate();
            if (base.ItemTemplate == null)
            {
                this._elementComboHeader.ContentTemplate = this.GetDefaultDataTemplate();
            }
            this.OnCaretBrushChanged(this.CaretBrush);
        }

        public override void OnApplyTemplate()
        {
            string errors = string.Empty;
            base.OnApplyTemplate();
            this._isLoaded = true;
            this._elementComboHeader = this.GetTemplateChild<TextEditableContentControl>("ComboHeader", true, ref errors);
            if (this._elementComboHeader != null)
            {
                this.InitializeComboHeaderPart();
            }
            this._elementScrollViewer = this.GetTemplateChild<System.Windows.Controls.ScrollViewer>("ScrollViewer", true, ref errors);
            if (this._elementScrollViewer != null)
            {
                this.InitializeScrollViewerPart();
            }
            this._elementDropDown = this.GetTemplateChild<DropDown>("DropDown", true, ref errors);
            if (this._elementDropDown != null)
            {
                this.InitializeDropDownPart();
            }
            this._elementHeaderClickInterceptor = this.GetTemplateChild<FrameworkElement>("HeaderClickInterceptor", false, ref errors);
            if (this._elementHeaderClickInterceptor != null)
            {
                this.InitializeHeaderClickInterceptorPart();
            }
            if (!string.IsNullOrEmpty(errors))
            {
                this._isLoaded = false;
                if ((base.Template != null) && !PlatformIndependent.IsInDesignMode(this))
                {
                    throw new InvalidOperationException(string.Format(CultureInfo.InvariantCulture, "Template cannot be applied to ComboBox.\nDetails: {0}", new object[] { errors }));
                }
            }
            else
            {
                this.ChangeVisualStateDropDownOpen(false);
                this.ChangeVisualStateCommon(false);
                this.ChangeVisualStateFocus(false);
                this.OnAfterApplyTemplate();
            }
        }

        private void OnAutoCompleteChanged(bool old)
        {
            this.UpdateIsReadOnly();
            this.UpdateHeaderClickInterceptor();
        }

        private static void OnAutoCompletePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox box = d as ComboBox;
            bool oldValue = (bool)e.OldValue;
            box.OnAutoCompleteChanged(oldValue);
        }

        private void OnCaretBrushChanged(Brush oldValue)
        {
            if (this._elementComboHeader != null)
            {
                this._elementComboHeader.CaretBrush = CloneBrush(this.CaretBrush);
            }
        }

        private static void OnCaretBrushPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox box = d as ComboBox;
            Brush oldValue = (Brush)e.OldValue;
            box.OnCaretBrushChanged(oldValue);
        }

        private void OnConditionChanged(object oldvalue)
        {
            this.ReloadItems();
            this.ClearFilterItemVisualState();
        }

        private static void OnConditionPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox box = d as ComboBox;
            Condition oldValue = (Condition)e.OldValue;
            box.OnConditionChanged(oldValue);
        }

        protected virtual void OnEditCompleted()
        {
            if (this.EditCompleted != null)
            {
                this.EditCompleted(this, new EventArgs());
            }
        }

        private static void OnForceMouseOverPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            (d as ComboBox).ChangeVisualStateCommon(true);
        }

        private void OnGotFocus(object sender, RoutedEventArgs e)
        {
            if (this._isLoaded && (e.OriginalSource == this))
            {
                if (this._itemClick)
                {
                    this._changed = false;
                }
                this._elementComboHeader.LostFocus -= new RoutedEventHandler(this._elementComboHeader_LostFocus);
                this._elementComboHeader.LostFocus += new RoutedEventHandler(this._elementComboHeader_LostFocus);
                this._elementComboHeader.IsTabStop = true;
                this._elementComboHeader.Focus();
                base.IsTabStop = false;
            }
        }

        private void OnIsDropDownOpenChanged(bool oldValue)
        {
            Action a = null;
            Action action2 = null;
            if (!base.IsEnabled)
            {
                this.IsDropDownOpen = false;
            }
            if (this._isLoaded)
            {
                if (!this._displayDDL)
                {
                    this._elementComboHeader.IsInEditMode = false;
                    if (a == null)
                    {
                        a = () => base.Focus();
                    }
                    base.Dispatcher.BeginInvoke(a);
                    this._elementComboHeader.IsInEditMode = true;
                    this.UpdateSwappedOut();
                }
                this._elementDropDown.IsDropDownOpen = this.IsDropDownOpen;
                if (((this.SelectionCommitted != null) && !this.IsDropDownOpen) && this._changed)
                {
                    this.OnSelectionCommitted();
                }
                if (action2 == null)
                {
                    action2 = () => this.ScrollSelectedIntoView();
                }
                base.Dispatcher.BeginInvoke(action2);
            }
        }

        private static void OnIsDropDownOpenPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox sender = d as ComboBox;
            bool oldValue = (bool)e.OldValue;
            sender.OnIsDropDownOpenChanged(oldValue);
            if ((sender.IsDropDownOpenChanged != null) && sender._throwIsDropDownOpenChanged)
            {
                PropertyChangedEventArgs<bool> args = new PropertyChangedEventArgs<bool>
                {
                    OldValue = (bool)e.OldValue,
                    NewValue = (bool)e.NewValue
                };
                sender.IsDropDownOpenChanged(sender, args);
            }
            sender.ChangeVisualStateDropDownOpen(true);
        }

        private void OnIsEditableChanged(bool oldValue)
        {
            this.UpdateIsReadOnly();
            this.UpdateHeaderClickInterceptor();
        }

        private static void OnIsEditablePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox box = d as ComboBox;
            bool oldValue = (bool)e.OldValue;
            box.OnIsEditableChanged(oldValue);
        }

        private void OnIsEnabledChanged(object sender, DependencyPropertyChangedEventArgs args)
        {
            if (this._isLoaded)
            {
                this._elementComboHeader.IsTabStop = base.IsEnabled;
            }
        }

        private static void OnIsFocusedPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            (d as ComboBox).ChangeVisualStateFocus(true);
        }

        private static void OnIsMouseOverPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox sender = d as ComboBox;
            if ((sender.IsMouseOverChanged != null) && sender._throwIsMouseOverChanged)
            {
                PropertyChangedEventArgs<bool> args = new PropertyChangedEventArgs<bool>
                {
                    OldValue = (bool)e.OldValue,
                    NewValue = (bool)e.NewValue
                };
                sender.IsMouseOverChanged(sender, args);
            }
            sender.ChangeVisualStateCommon(true);
        }

        private void OnItemConverterChanged(TypeConverter oldValue)
        {
            this._myConverterBridge.Converter = this.ItemConverter;
            if (this._elementComboHeader != null)
            {
                this._elementComboHeader.ContentConverter = this._myConverterBridge;
            }
        }

        private static void OnItemConverterPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox box = d as ComboBox;
            TypeConverter oldValue = (TypeConverter)e.OldValue;
            box.OnItemConverterChanged(oldValue);
        }

        protected override void OnItemsChanged(NotifyCollectionChangedEventArgs e)
        {
            if (!this._changeItemsInternal)
            {
                base.OnItemsChanged(e);
                int selectedIndex = this.SelectedIndex;
                if ((0 <= this._desiredIndex) && (this._desiredIndex < base.Items.Count))
                {
                    this.SelectedIndex = this._desiredIndex;
                }
                else if (this.SelectedItem != null)
                {
                    this._setting = true;
                    this.SelectedIndex = this.MyIndexOf(this.SelectedItem);
                    this._setting = false;
                }
                else if (this.SelectedValue != null)
                {
                    this.UpdateFromSelectedValue();
                }
                this._tempItems.Clear();
                if ((this.SelectedIndex == -1) && (selectedIndex != -1))
                {
                    this.SelectedItem = null;
                }
                foreach (object obj2 in base.Items)
                {
                    this._tempItems.Add(obj2);
                    ComboBoxItem item = obj2 as ComboBoxItem;
                    if ((item != null) && item.IsSelected)
                    {
                        this.SelectedItem = item;
                    }
                }
            }
        }

        private void OnLostFocus(object sender, RoutedEventArgs e)
        {
            if (this._isLoaded)
            {
                FrameworkElement descendant = this._elementComboHeader.GetLogicalFocusedElement();
                if (!this.IsVisualOrLogicalParentOf(descendant))
                {
                    this.IsDropDownOpen = false;
                }
            }
        }

        protected override void OnMouseLeftButtonDown(MouseButtonEventArgs e)
        {
            base.OnMouseLeftButtonDown(e);
            if (!e.Handled)
            {
                e.Handled = true;
                base.Focus();
            }
        }

        private void OnSelectedIndexChanged(int oldValue)
        {
            if (!this._setting)
            {
                if (this.SelectedIndex == -1)
                {
                    this.SelectedItem = null;
                    this._desiredIndex = -1;
                }
                else if (this.SelectedIndex < -1)
                {
                    this.SelectedIndex = -1;
                }
                else if (this.SelectedIndex >= base.Items.Count)
                {
                    if (!DesignerProperties.GetIsInDesignMode(this))
                    {
                        int selectedIndex = this.SelectedIndex;
                        this.SelectedIndex = -1;
                        this._desiredIndex = selectedIndex;
                    }
                }
                else
                {
                    this.SelectedItem = base.Items[this.SelectedIndex];
                    this._desiredIndex = -1;
                }
            }
            this.ScrollSelectedIntoView();
        }

        private static void OnSelectedIndexPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox sender = d as ComboBox;
            int oldValue = (int)e.OldValue;
            sender.OnSelectedIndexChanged(oldValue);
            if ((sender.SelectedIndexChanged != null) && sender._throwSelectedIndexChanged)
            {
                PropertyChangedEventArgs<int> args = new PropertyChangedEventArgs<int>
                {
                    OldValue = (int)e.OldValue,
                    NewValue = (int)e.NewValue
                };
                sender.SelectedIndexChanged(sender, args);
            }
        }

        private void OnSelectedItemChanged(object oldValue)
        {
            if (!this._setting)
            {
                this._setting = true;
                this.SetIsSelected(oldValue, false);
                this.SelectedIndex = this.MyIndexOf(this.SelectedItem);
                this._desiredIndex = -1;
                this.Text = this._myConverterBridge.ConvertToString(this.SelectedItem);
                this.UpdateSwappedOut();
                this.UpdateHeaderTemplate();
                if (string.IsNullOrEmpty(this.SelectedValuePath))
                {
                    this.SelectedValue = this.SelectedItem;
                }
                else
                {
                    this.SelectedValue = this.SelectedItem.GetPropertyValue<object>(this.SelectedValuePath);
                }
                this.SetIsSelected(this.SelectedItem, true);
                this._setting = false;
                if (this.SelectionCommitted != null)
                {
                    if (this.IsDropDownOpen)
                    {
                        this._changed = true;
                    }
                    else
                    {
                        this.OnSelectionCommitted();
                    }
                }
            }
        }

        private static void OnSelectedItemPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox sender = d as ComboBox;
            object oldValue = e.OldValue;
            sender.OnSelectedItemChanged(oldValue);
            if ((sender.SelectedItemChanged != null) && sender._throwSelectedItemChanged)
            {
                PropertyChangedEventArgs<object> args = new PropertyChangedEventArgs<object>
                {
                    OldValue = e.OldValue,
                    NewValue = e.NewValue
                };
                sender.SelectedItemChanged(sender, args);
            }
        }

        private void OnSelectedValueChanged(object oldValue)
        {
            if (!this._setting)
            {
                this.UpdateFromSelectedValue();
            }
        }

        private static void OnSelectedValuePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox sender = d as ComboBox;
            object oldValue = e.OldValue;
            sender.OnSelectedValueChanged(oldValue);
            if ((sender.SelectedValueChanged != null) && sender._throwSelectedValueChanged)
            {
                PropertyChangedEventArgs<object> args = new PropertyChangedEventArgs<object>
                {
                    OldValue = e.OldValue,
                    NewValue = e.NewValue
                };
                sender.SelectedValueChanged(sender, args);
            }
        }

        protected virtual void OnSelectionCommitted()
        {
            if (this.SelectionCommitted != null)
            {
                PropertyChangedEventArgs<object> e = new PropertyChangedEventArgs<object>
                {
                    NewValue = this.SelectedItem
                };
                this.SelectionCommitted(this, e);
            }
        }

        private void OnTextChanged(string oldValue)
        {
            if (!this._setting)
            {
                this._isSettingText = true;
                this.SelectedItem = this._myConverterBridge.ConvertFromStringToItem(this.Text);
                this._isSettingText = false;
            }
        }

        private static void OnTextPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ComboBox box = d as ComboBox;
            string oldValue = (string)e.OldValue;
            box.OnTextChanged(oldValue);
        }

        protected override void PrepareContainerForItemOverride(DependencyObject element, object item)
        {
            base.PrepareContainerForItemOverride(element, item);
            ComboBoxItem container = (ComboBoxItem)element;
            if (!object.ReferenceEquals(element, item))
            {
                container.Item = item;
            }
            object obj2 = (container == item) ? container.Content : item;
            DataTemplate itemTemplate = null;
            if (this.ItemTemplateSelector != null)
            {
                itemTemplate = this.ItemTemplateSelector.SelectTemplate(obj2, container);
            }
            if (base.ItemTemplate != null)
            {
                itemTemplate = base.ItemTemplate;
            }
            if (container == item)
            {
                if (container.ContentTemplateSelector != null)
                {
                    itemTemplate = container.ContentTemplateSelector.SelectTemplate(obj2, container);
                }
                if (container.ContentTemplate != null)
                {
                    itemTemplate = container.ContentTemplate;
                }
            }
            if ((itemTemplate != null) && (base.ItemsSource != null))
            {
                container.ContentTemplate = itemTemplate;
            }
            int num = base.ItemContainerGenerator.IndexFromContainer(element);
            if (num != -1)
            {
                if (num == this.SelectedIndex)
                {
                    container.IsSelected = true;
                }
                else
                {
                    container.IsSelected = false;
                }
            }
            container.IsMouseOver = false;
            if ((this.ItemContainerStyle != null) && (container.Style == null))
            {
                container.Style = this.ItemContainerStyle;
            }
            container.SetBinding<ComboBox>(Control.FontFamilyProperty, this, cmb => cmb.FontFamily);
            container.SetBinding<ComboBox>(Control.FontSizeProperty, this, cmb => cmb.FontSize);
            container.SetBinding<ComboBox>(Control.FontStretchProperty, this, cmb => cmb.FontStretch);
            container.SetBinding<ComboBox>(Control.FontStyleProperty, this, cmb => cmb.FontStyle);
            container.SetBinding<ComboBox>(Control.FontWeightProperty, this, cmb => cmb.FontWeight);
            container.SetBinding<ComboBox>(Control.ForegroundProperty, this, cmb => cmb.Foreground);
            container.SetBinding<ComboBox>(Control.BackgroundProperty, this, cmb => cmb.Background);
            container.SetBinding<ComboBox>(Control.BorderBrushProperty, this, cmb => cmb.BorderBrush);
            container.SetBinding<ComboBox>(ComboBoxItem.SelectedBackgroundProperty, this, cmb => cmb.SelectedBackground);
            container.SetBinding<ComboBox>(ComboBoxItem.MouseOverBrushProperty, this, cmb => cmb.MouseOverBrush);
            container.MouseLeftButtonUp -= new MouseButtonEventHandler(this.handle_ItemClick);
            container.MouseLeftButtonUp += new MouseButtonEventHandler(this.handle_ItemClick);
        }

        private void ReloadItems()
        {
            if (!PlatformIndependent.IsInDesignMode(this))
            {
                this._changeItemsInternal = true;
                if (base.ItemsSource != null)
                {
                    base.ItemsSource = this._tempItems;
                }
                else if (base.Items != null)
                {
                    base.Items.Clear();
                    foreach (object obj2 in this._tempItems)
                    {
                        base.Items.Add(obj2);
                    }
                }
                this._changeItemsInternal = false;
            }
        }

        private void ScrollSelectedIntoView()
        {
            if ((((this._elementScrollViewer != null) && (this.SelectedIndex >= 0)) && this.IsDropDownOpen) && !this.IsOnCurrentPage(this.SelectedIndex))
            {
                if ((this._elementScrollViewer.VerticalOffset - this.SelectedIndex) > 0.0)
                {
                    this._elementScrollViewer.ScrollToVerticalOffset((double)this.SelectedIndex);
                }
                else
                {
                    this._elementScrollViewer.ScrollToVerticalOffset((this.SelectedIndex - this._elementScrollViewer.ViewportHeight) + 1.0);
                }
            }
        }

        private void SetCustomDefaultValues()
        {
            base.SetBinding(DisplayMemberPathShadowProperty, new Binding().From<ComboBox>(this, x => x.DisplayMemberPath));
            base.SetBinding(ItemTemplateShadowProperty, new Binding().From<ComboBox>(this, x => x.ItemTemplate));
            this._myConverterBridge = new ComboBoxItemConverterBridge(this);
            this.ItemConverter = new ComboBoxItemConverterBridge(this);
            base.GotFocus += new RoutedEventHandler(this.OnGotFocus);
            base.LostFocus += new RoutedEventHandler(this.OnLostFocus);
            base.IsEnabledChanged += new DependencyPropertyChangedEventHandler(this.OnIsEnabledChanged);
            base.SizeChanged += (param0, param1) => this.UpdateMinDropDownWidth();
        }

        private void SetIsSelected(object item, bool selected)
        {
            ComboBoxItem item2 = item as ComboBoxItem;
            if (item2 == null)
            {
                item2 = base.ItemContainerGenerator.ContainerFromItem(item) as ComboBoxItem;
            }
            if (item2 != null)
            {
                item2.IsSelected = selected;
            }
        }

        internal void SetTextInput(string oldValue, string newValue, bool executeStartWith)
        {
            if (string.IsNullOrEmpty(newValue))
            {
                this.SelectedItem = null;
            }
            else
            {
                bool flag = true;
                if (!this.IsEditable || (this.Condition == Condition.Contains))
                {
                    string str;
                    if (this.FindString(newValue, true, executeStartWith, out str))
                    {
                        newValue = str;
                    }
                    else
                    {
                        flag = false;
                    }
                }
                if (flag)
                {
                    this.Text = newValue;
                }
                else
                {
                    this.Text = oldValue;
                }
            }
        }

        private void UpdateFromSelectedValue()
        {
            foreach (object obj2 in base.Items)
            {
                if ((string.IsNullOrEmpty(this.SelectedValuePath) && object.Equals(this.SelectedValue, this.SelectedItem)) || (!string.IsNullOrEmpty(this.SelectedValuePath) && object.Equals(this.SelectedValue, obj2.GetPropertyValue<object>(this.SelectedValuePath))))
                {
                    this.SelectedItem = obj2;
                    return;
                }
            }
            this.SelectedItem = null;
            this.SelectedIndex = -1;
        }

        private void UpdateHeaderClickInterceptor()
        {
            if (this._elementHeaderClickInterceptor != null)
            {
                this._elementHeaderClickInterceptor.IsHitTestVisible = !this.AutoComplete && !this.IsEditable;
            }
        }

        private void UpdateHeaderTemplate()
        {
            if (this._elementComboHeader != null)
            {
                DataTemplate contentTemplate;
                ComboBoxItem selectedItem = this.SelectedItem as ComboBoxItem;
                if (selectedItem != null)
                {
                    contentTemplate = selectedItem.ContentTemplate;
                }
                else if (string.IsNullOrEmpty(base.DisplayMemberPath) && (base.ItemsSource != null))
                {
                    contentTemplate = base.ItemTemplate;
                }
                else
                {
                    contentTemplate = this.GetDefaultDataTemplate();
                }
                this._elementComboHeader.ContentTemplate = contentTemplate;
            }
        }

        private void UpdateIsReadOnly()
        {
            if (this._elementComboHeader != null)
            {
                bool flag;
                if (this.AutoComplete)
                {
                    flag = false;
                }
                else if (this.IsEditable)
                {
                    flag = false;
                }
                else
                {
                    flag = true;
                }
                this._elementComboHeader.IsReadOnly = flag;
                this._elementComboHeader.UpdateIsReadOnly();
            }
        }

        private void UpdateMinDropDownWidth()
        {
            if (this._elementDropDown != null)
            {
                this._elementDropDown.SetValue(DropDownButton.MinDropDownWidthProperty, base.ActualWidth);
            }
        }

        private void UpdateSwappedOut()
        {
            if (this._elementComboHeader != null)
            {
                this._elementComboHeader.IsDropDownOpen = this.IsDropDownOpen;
                ComboBoxItem container = null;
                if (DesignerProperties.GetIsInDesignMode(this))
                {
                    object actualContent = this._elementComboHeader.ActualContent;
                    this._elementComboHeader.ActualContent = null;
                    this._elementComboHeader.UpdateIsWatermarked();
                    this._elementComboHeader.UpdateVisualState();
                    if (this.SwappedOutItem != null)
                    {
                        this.SwappedOutItem.SwappedOut = false;
                        this.SwappedOutItem.Content = actualContent;
                        this.SwappedOutItem = null;
                    }
                    if (this.SelectedItem != null)
                    {
                        int selectedIndex = this.SelectedIndex;
                        bool isNewlyRealized = false;
                        System.Windows.Controls.ItemContainerGenerator itemContainerGenerator = base.ItemContainerGenerator;
                        IItemContainerGenerator generator2 = itemContainerGenerator;
                        container = (ComboBoxItem)itemContainerGenerator.ContainerFromIndex(selectedIndex);
                        if (container == null)
                        {
                            GeneratorPosition position = itemContainerGenerator.GeneratorPositionFromIndex(selectedIndex);
                            using (generator2.StartAt(position, GeneratorDirection.Forward, true))
                            {
                                container = (ComboBoxItem)generator2.GenerateNext(out isNewlyRealized);
                            }
                        }
                        if (isNewlyRealized)
                        {
                            generator2.PrepareItemContainer(container);
                        }
                        if ((this.SelectedIndex != -1) && !this.IsDropDownOpen)
                        {
                            this.SwappedOutItem = container;
                            container.SwappedOut = true;
                            actualContent = container.Content;
                            container.Content = null;
                            this._elementComboHeader.ActualContent = actualContent;
                        }
                        if (!string.IsNullOrEmpty(this.Text) && (this._elementComboHeader.ActualContent == null))
                        {
                            this._elementComboHeader.ActualContent = this.Text;
                        }
                        this._elementComboHeader.IsDirty = false;
                    }
                }
                else
                {
                    this._elementComboHeader.ActualContent = null;
                    this._elementComboHeader.UpdateIsWatermarked();
                    this._elementComboHeader.UpdateVisualState();
                    if (this.SwappedOutItem != null)
                    {
                        this.SwappedOutItem.SwappedOut = false;
                        this.SwappedOutItem = null;
                    }
                    if (this.SelectedItem != null)
                    {
                        if (this.SelectedIndex != -1)
                        {
                            container = (ComboBoxItem)base.ItemContainerGenerator.ContainerFromIndex(this.SelectedIndex);
                            if ((container != null) && !this.IsDropDownOpen)
                            {
                                this.SwappedOutItem = container;
                                container.SwappedOut = true;
                            }
                        }
                        if (container == null)
                        {
                            container = this.SelectedItem as ComboBoxItem;
                        }
                        if (container == null)
                        {
                            this._elementComboHeader.ActualContent = this.SelectedItem;
                        }
                        else
                        {
                            this._elementComboHeader.ActualContent = container.Content;
                        }
                        this._elementComboHeader.IsDirty = false;
                    }
                }
            }
        }

        // Properties
        public bool AutoComplete
        {
            get { return (bool)GetValue(AutoCompleteProperty); }
            set { SetValue(AutoCompleteProperty, value); }
        }

        public Brush ButtonBackground
        {
            get { return (Brush)GetValue(ButtonBackgroundProperty); }
            set { SetValue(ButtonBackgroundProperty, value); }
        }

        public Brush ButtonForeground
        {
            get { return (Brush)GetValue(ButtonForegroundProperty); }
            set { SetValue(ButtonForegroundProperty, value); }
        }

        public Brush CaretBrush
        {
            get { return (Brush)GetValue(CaretBrushProperty); }
            set { SetValue(CaretBrushProperty, value); }
        }

        public Condition Condition
        {
            get { return (Condition)GetValue(ConditionProperty); }
            set { SetValue(ConditionProperty, value); }
        }

        public CornerRadius CornerRadius
        {
            get { return (CornerRadius)GetValue(CornerRadiusProperty); }
            set { SetValue(CornerRadiusProperty, value); }
        }

        public Visibility DisabledCuesVisibility
        {
            get { return (Visibility)GetValue(DisabledCuesVisibilityProperty); }
            set { SetValue(DisabledCuesVisibilityProperty, value); }
        }

        public DropDownDirection DropDownDirection
        {
            get { return (DropDownDirection)GetValue(DropDownDirectionProperty); }
            set { SetValue(DropDownDirectionProperty, value); }
        }

        public double DropDownHeight
        {
            get { return (double)GetValue(DropDownHeightProperty); }
            set { SetValue(DropDownHeightProperty, value); }
        }

        public double DropDownWidth
        {
            get { return (double)GetValue(DropDownWidthProperty); }
            set { SetValue(DropDownWidthProperty, value); }
        }

        public Brush FocusBrush
        {
            get { return (Brush)GetValue(FocusBrushProperty); }
            set { SetValue(FocusBrushProperty, value); }
        }

        public Visibility FocusCuesVisibility
        {
            get { return (Visibility)GetValue(FocusCuesVisibilityProperty); }
            set { SetValue(FocusCuesVisibilityProperty, value); }
        }

        internal bool ForceMouseOver
        {
            get { return (bool)GetValue(ForceMouseOverProperty); }
            set { SetValue(ForceMouseOverProperty, value); }
        }

        public bool IsDropDownOpen
        {
            get { return (bool)GetValue(IsDropDownOpenProperty); }
            set { SetValue(IsDropDownOpenProperty, value); }
        }

        public bool IsEditable
        {
            get { return (bool)GetValue(IsEditableProperty); }
            set { SetValue(IsEditableProperty, value); }
        }

        public bool IsFocused
        {
            get { return (bool)GetValue(IsFocusedProperty); }
            set { SetValue(IsFocusedProperty, value); }
        }

        public bool IsMouseOver
        {
            get { return (bool)GetValue(IsMouseOverProperty); }
            set { SetValue(IsMouseOverProperty, value); }
        }

        public Style ItemContainerStyle
        {
            get { return (Style)GetValue(ItemContainerStyleProperty); }
            set { SetValue(ItemContainerStyleProperty, value); }
        }

        public TypeConverter ItemConverter
        {
            get { return (TypeConverter)GetValue(ItemConverterProperty); }
            set { SetValue(ItemConverterProperty, value); }
        }

        public DataTemplateSelector ItemTemplateSelector
        {
            get { return (DataTemplateSelector)GetValue(ItemTemplateSelectorProperty); }
            set { SetValue(ItemTemplateSelectorProperty, value); }
        }

        public double MaxDropDownHeight
        {
            get { return (double)GetValue(MaxDropDownHeightProperty); }
            set { SetValue(MaxDropDownHeightProperty, value); }
        }

        public double MaxDropDownWidth
        {
            get { return (double)GetValue(MaxDropDownWidthProperty); }
            set { SetValue(MaxDropDownWidthProperty, value); }
        }

        public Brush MouseOverBrush
        {
            get { return (Brush)GetValue(MouseOverBrushProperty); }
            set { SetValue(MouseOverBrushProperty, value); }
        }

        public Brush PressedBrush
        {
            get { return (Brush)GetValue(PressedBrushProperty); }
            set { SetValue(PressedBrushProperty, value); }
        }

        public Style ScrollBarStyle
        {
            get { return (Style)GetValue(ScrollBarStyleProperty); }
            set { SetValue(ScrollBarStyleProperty, value); }
        }

        public Brush SelectedBackground
        {
            get { return (Brush)GetValue(SelectedBackgroundProperty); }
            set { SetValue(SelectedBackgroundProperty, value); }
        }

        public int SelectedIndex
        {
            get { return (int)GetValue(SelectedIndexProperty); }
            set { SetValue(SelectedIndexProperty, value); }
        }

        public object SelectedItem
        {
            get { return GetValue(SelectedItemProperty); }
            set { SetValue(SelectedItemProperty, value); }
        }

        public object SelectedValue
        {
            get { return GetValue(SelectedValueProperty); }
            set { SetValue(SelectedValueProperty, value); }
        }

        public string SelectedValuePath
        {
            get { return (string)GetValue(SelectedValueProperty); }
            set { SetValue(SelectedValueProperty, value); }
        }

        public Brush SelectionBackground
        {
            get { return (Brush)GetValue(SelectionBackgroundProperty); }
            set { SetValue(SelectionBackgroundProperty, value); }
        }

        public Brush SelectionForeground
        {
            get { return (Brush)GetValue(SelectionForegroundProperty); }
            set { SetValue(SelectionForegroundProperty, value); }
        }

        public string Text
        {
            get { return (string)GetValue(TextProperty); }
            set { SetValue(TextProperty, value); }
        }

        public TextAlignment TextAlignment
        {
            get { return (TextAlignment)GetValue(TextAlignmentProperty); }
            set { SetValue(TextAlignmentProperty, value); }
        }

        public Style ValidationDecoratorStyle
        {
            get { return (Style)GetValue(ValidationDecoratorStyleProperty); }
            set { SetValue(ValidationDecoratorStyleProperty, value); }
        }

        public object Watermark
        {
            get { return GetValue(WatermarkProperty); }
            set { SetValue(WatermarkProperty, value); }
        }
    }

    public enum Condition
    {
        StartWith,
        Contains
    }
}
